//
//  PoolingModel.m
//  tEngineTechDemo
//
//  Created by Gareth Williams on 16/01/2012.
//  Copyright (c) 2012 __MyCompanyName__. All rights reserved.
//
//  creates a pool of objects that conform to the poolable protocol

#import "PoolingModel.h"

@interface PoolingModel()

@property(readonly, nonatomic, retain) Class<PoolableFactory> factory;
          
-(void)fillPoolToSize:(int)size;
-(void)emptyPool;

@end

@implementation PoolingModel 

@synthesize pool = _pool;
@synthesize maxPoolSize = _maxPoolSize;
@synthesize factory = _factory;

-(id)initWithFactory:(Class<PoolableFactory>)factoryToUse PoolSize:(int)size withMaxSize:(int)maxSize
{
    self = [super init];
    if (self) 
    {
        _factory = factoryToUse;
        _maxPoolSize = maxSize;
        [self fillPoolToSize:size];
    }
    return self;
}

- (void)dealloc 
{
    [self emptyPool];
    [super dealloc];
}

#pragma mark -

-(void)checkIn:(id<Poolable>)object
{
    [object clean];
    //if(_pool.count < _maxPoolSize) [_pool addObject:object];
    [_pool addObject:object];
    
    //NSLog(@"checkin %i", _pool.count);
}

-(id<Poolable>)checkOut
{
    //NSLog(@"checkout %i", _pool.count);
    
    if(_pool.count <= 0) [self fillPoolToSize:10];
    
    id<Poolable> entity = [_pool lastObject];
    [[entity retain] autorelease];
    
    [_pool removeLastObject]; //will be autoreleased following function block
    
    return entity;
}

#pragma mark helpers

-(void)fillPoolToSize:(int)size
{
    //NSLog(@"*** refilling pool:%i ***", size);
    if(_pool == nil) _pool = [[NSMutableArray alloc] init];
    
    //while (_pool.count < size && _pool.count < _maxPoolSize)
    while (size > 0)
    {
        id<Poolable> p = [_factory create]; //auto release ?
        [_pool addObject:p]; //retain
        size--;
    }
}

-(void)emptyPool
{
    [_pool removeAllObjects]; //release
}

@end
